package base.reflect;

import com.google.common.collect.Lists;
import org.reflections.Reflections;
import org.reflections.scanners.FieldAnnotationsScanner;
import org.reflections.scanners.MethodAnnotationsScanner;
import org.reflections.scanners.MethodParameterScanner;
import org.reflections.scanners.SubTypesScanner;
import org.reflections.util.ConfigurationBuilder;

import java.lang.reflect.Field;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Map;
import java.util.Set;

public class InvocationHandlerDemo {
    public static void main(String[] args) throws NoSuchFieldException, IllegalAccessException {
        Reflections reflections = new Reflections(new ConfigurationBuilder()
                .forPackages("base") // 指定路径URL
                .addScanners(new SubTypesScanner()) // 添加子类扫描工具
                .addScanners(new FieldAnnotationsScanner()) // 添加 属性注解扫描工具
                .addScanners(new MethodAnnotationsScanner() ) // 添加 方法注解扫描工具
                .addScanners(new MethodParameterScanner() ) // 添加方法参数扫描工具
        );

        Set<Method> methodSet = reflections.getMethodsAnnotatedWith(MyAnnotation.class);
        if (!methodSet.isEmpty()) {
            for (Method method : methodSet) {
                MyAnnotation myAnnotation = method.getAnnotation(MyAnnotation.class);
                InvocationHandler invocationHandler = Proxy.getInvocationHandler(myAnnotation);
                Field memberValuesField = invocationHandler.getClass().getDeclaredField("memberValues");
                memberValuesField.setAccessible(true);

                Map<String, Object> memberValues = (Map<String, Object>)memberValuesField.get(invocationHandler);
                String[] ids = (String[])memberValues.get("ids");
                System.out.println("修改前ids：" + Lists.newArrayList(ids));
                for (int i = 0; i < ids.length; i++) {
                    ids[i] = "Changed: " + ids[i];
                }
                memberValues.put("ids", ids);
                System.out.println("修改后ids：" + Lists.newArrayList(myAnnotation.ids()));
            }
        }
    }
}
